import React, { FC, useEffect, useState, useRef, useMemo } from "react";
import { useSearchParams } from "react-router-dom";
import { useDebounceFn, useRequest } from "ahooks";
import styles from "../../../assets/css/common.module.scss";
// import { data } from "./data.js";
import { Typography, Spin, Empty } from "antd";
import QuestionCard from "../../../components/questionCard.js";
import ListSearch from "../../../components/ListSearch";
import { getQuestionList } from "../../../services/question";
// 为了实现上划加载更多，需要新的方式
// import useSearchQuestionData from "../../../hooks/useSearchQuestionData";
import { LIST_PAGE_SIZE, LIST_SEARCH_PARAM_KEY } from "../../../constant/index";

interface QuestionItem {
  _id: string;
  title: string;
  isPublished: boolean;
  isStar: boolean;
  answerCount: number;
  creatdAt: string;
  isDeleted?: boolean;
}

const { Title } = Typography;
const List: FC = () => {
  // 优化
  const [start, setStart] = useState(false); //是否开启加载(防抖)
  // const [questionList, setQuestionList] = useState(data);
  // 为了实现上划加载更多，需要新的方式
  // const { loading, data = {} } = useSearchQuestionData();
  // const { list = [], total = 0 } = data;
  const [list, setList] = useState<QuestionItem[]>([]);
  const [page, setPage] = useState(1);
  const [total, setTotal] = useState(0);
  const havaMore = total > list.length;
  const [searchParams] = useSearchParams();
  const keyword = searchParams.get(LIST_SEARCH_PARAM_KEY) || "";
  // 查询功能
  useEffect(() => {
    setStart(false);
    setPage(1);
    setList([]);
    setTotal(0);
  }, [keyword]);

  // 获取接口数据
  async function fn() {
    const data = await getQuestionList({
      page,
      pageSize: LIST_PAGE_SIZE,
      keyword,
    });
    return data;
  }
  const { run: load, loading } = useRequest(fn, {
    manual: true, // 手动触发
    onSuccess: (res) => {
      const { list: l = [], total = 0 } = res;
      setList(list.concat(l));
      setTotal(total);
      setPage(page + 1);
    },
  });

  // 触发加载
  // function tryLoadMore() {
  //   console.log("触发加载");
  // }
  const containerRef = useRef<HTMLDivElement>(null);
  // 使用ahooks防抖
  const { run: tryLoadMore } = useDebounceFn(
    () => {
      const elem = containerRef.current;
      // 如果元素不存在，直接返回
      if (elem == null) return;
      // DomAPI，返回一个domRect对象，其提供了子元素的大小及其相对于视口的位置
      const domRect = elem.getBoundingClientRect();
      if (domRect == null) return;
      const { bottom } = domRect; // 获取元素距离视口顶部的距离
      if (bottom <= document.body.clientHeight) {
        load(); // 真正加载数据
        setStart(true);
      }
    },
    { wait: 1000 }
  );
  // 1. 当页面加载，或者url参数（keyword）变化时，触发加载
  useEffect(() => {
    // 加载第一页
    tryLoadMore();
  }, [searchParams]);
  // 2. 监听上划加载
  useEffect(() => {
    if (havaMore) {
      window.addEventListener("scroll", tryLoadMore);
    }
    return () => {
      window.removeEventListener("scroll", tryLoadMore); // 解绑事件
    };
  }, [searchParams, havaMore]);

  // 加载更多元素
  /**
   * useMemo()用于执行 memoization（记忆化），即缓存计算结果以避免在每次渲染时都重新计算
   */
  const LoadMoreContentElem = useMemo(() => {
    if (!start || loading) return <Spin size="large" />;
    if (total === 0) return <Empty description="暂无数据" />;
    if (!havaMore) return <span>没有更多了</span>;
    return <span>开始加载下一页</span>;
  }, [start, loading, havaMore]);

  return (
    <>
      <div className={styles.box}>
        <div className={styles.header}>
          <Title level={3}>我的问卷⌛️</Title>
          {/* <div className={styles.right}>搜索框</div> */}
          <ListSearch />
        </div>

        <div className={styles.container}>
          {/* {loading && (
            <div style={{ textAlign: "center" }}>
              <Spin size="large" />
            </div>
          )} */}
          {/* {!loading && */}
          {list.length > 0 &&
            list.map((item: QuestionItem) => {
              const { _id } = item;
              return <QuestionCard key={_id} {...item} />;
            })}
        </div>

        <div className={styles.footer}>
          <div ref={containerRef}>{LoadMoreContentElem}</div>
        </div>
      </div>
    </>
  );
};

export default List;
